package com.hyzh.latte.vehicle.controller;

import cn.hutool.core.collection.CollectionUtil;
import cn.hutool.core.util.StrUtil;
import com.coffee.concurrent.CoffeeExecutorManager;
import com.coffee.core.CoffeeResponse;
import com.hyzh.latte.util.LatteResponseCode;
import com.hyzh.latte.util.StringKits;
import com.hyzh.latte.util.gather.EarlyWarningPublicDTO;
import com.hyzh.latte.util.gather.OkhttpUtil;
import com.hyzh.latte.vehicle.dmo.*;
import com.hyzh.latte.vehicle.dmo.entity.ParkPGEntity;
import com.hyzh.latte.vehicle.nezha.NezhaPersonManager;
import com.hyzh.latte.vehicle.nezha.VehicleTrackHandler;
import lombok.AllArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.*;

import java.util.List;
import java.util.concurrent.Executor;
import java.util.stream.Collectors;

/**
 * 数据从算法组
 * 算法组 有数据 就会调用该接口
 * @author songkui
 * @since 2024/3/15 23:15
 */
@RestController
@RequestMapping("/source")
@Slf4j
@AllArgsConstructor
public class DataSourceController {

    private final VehicleTrackHandler vehicleTrackHandler;

    //header : park : 园区编码;
    @PostMapping("/vehicleTrack")
    public CoffeeResponse<String> vehicleTrack(@RequestHeader("park") String park, @RequestBody List<VehicleTrackDTO> data){

        if (StrUtil.isEmpty(park) || CollectionUtil.isEmpty(data)){
            log.error("handler>> park or data id  is null; park: {}", park);
            return CoffeeResponse.response(LatteResponseCode.ParamInvalid);
        }

        for (VehicleTrackDTO dto : data){
            if (StrUtil.isEmpty(dto.getCno()) || StrUtil.isEmpty(dto.getVno()) || !StringKits.isChinese(dto.getVno())){
                log.warn("handler>>  cameraNo or vehicleNo is null or vNo invalid; park: {}, VehicleTrackDTO：{}", park, dto);
            }else {
                Executor executor = CoffeeExecutorManager.getInstance().getDisruptor(dto.getVno().hashCode());
                executor = null == executor ? CoffeeExecutorManager.getInstance().getDefaultExecutor() : executor;
                executor.execute(() ->vehicleTrackHandler.track(park, dto));
            }
        }

        return CoffeeResponse.response(null, LatteResponseCode.Success);
    }

    @PostMapping("/vehicle-inout")
    public CoffeeResponse<String> trackInoutEnterprise(@RequestHeader("park") String park, @RequestBody VehicleInoutEnterpriseDTO data){

        if (CollectionUtil.isEmpty(data.getData())){
            log.error("track-inout>> park or data id  is null; park: {}", park);
            return CoffeeResponse.response(LatteResponseCode.ParamInvalid);
        }

        Executor executor = CoffeeExecutorManager.getInstance().getDisruptor(park.hashCode());
        executor = null == executor ? CoffeeExecutorManager.getInstance().getDefaultExecutor() : executor;
        executor.execute(() ->vehicleTrackHandler.doInOutEnterprises(park, data));

        return CoffeeResponse.response(null, LatteResponseCode.Success);
    }


    @PostMapping("/personTrack")
    public CoffeeResponse<String> personTrack(@RequestHeader("park") String park, @RequestBody List<PersonTrackDTO> data){

        if (StrUtil.isEmpty(park) || CollectionUtil.isEmpty(data)){
            log.error("personTrack handler>> park or data id  is null; park: {}", park);
            return CoffeeResponse.response(LatteResponseCode.ParamInvalid);
        }
        log.info("personTrack -> data size {}", data.size());

        Executor executor = CoffeeExecutorManager.getInstance().getDefaultExecutor();
        executor.execute(() -> NezhaPersonManager.getInstance().putData(park, data));

        return CoffeeResponse.response(LatteResponseCode.Success);
    }
    @PostMapping("/personAlarm")
    public CoffeeResponse<String> personAlarm(@RequestHeader("park") String park, @RequestBody List<PersonAlarmDTO> data){

        if (StrUtil.isEmpty(park) || CollectionUtil.isEmpty(data)){
            log.error("personAlarm handler>> park or data id  is null; park: {}", park);
            return CoffeeResponse.response(LatteResponseCode.ParamInvalid);
        }
        log.info("***personAlarm: ***{}***{}*", park, data.size());
        ParkPGEntity parkEntity = NezhaPersonManager.getInstance().parkPGEntity(park);
        if (null == parkEntity){
            log.error("personAlarm handler>> park  null; park: {}", park);
            return CoffeeResponse.response(LatteResponseCode.ParamInvalid);
        }
        log.info("personAlarm -> data size {}", data.size());
        Executor executor = CoffeeExecutorManager.getInstance().getDefaultExecutor();
        executor.execute(() -> {
            List<PersonGatherDTO> pl = data.stream().filter(g -> null != g.getNum() && g.getNum() >= parkEntity.getGatherNumber()).map(PersonAlarmDTO::buildPersonGatherDTO).collect(Collectors.toList());
            if (CollectionUtil.isNotEmpty(pl)){
                NezhaPersonManager.getInstance().putGatherData(park, pl);

                List<EarlyWarningPublicDTO> list = data.stream().filter(g -> null != g.getNum() && g.getNum() >= parkEntity.getGatherNumber()).map(x -> x.buildEarlyWarningPublicDTO(parkEntity)).collect(Collectors.toList());
                OkhttpUtil.doPost(list, parkEntity.getGatherUrl());
            }else {
                log.info("---personAlarm: person number < {}", parkEntity.getGatherNumber());
            }
        });

        return CoffeeResponse.response(LatteResponseCode.Success);
    }


}
